package com.xyw.code.gateway.web.events;

import com.alibaba.fastjson.JSON;
import com.rabbitmq.client.Channel;
import com.xyw.code.gateway.common.entity.enums.RouteDefinitionMessageTagEnum;
import com.xyw.code.gateway.common.entity.vo.RouteDefinitionMessage;
import com.xyw.code.gateway.web.config.BusConfig;
import com.xyw.code.gateway.web.service.IRouteService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.core.Base64UrlNamingStrategy;
import org.springframework.amqp.core.ExchangeTypes;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.gateway.route.RouteDefinition;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;

import java.io.IOException;
import java.nio.charset.StandardCharsets;

@Component
@Slf4j
public class BusReceiver {

    @Autowired
    private IRouteService routeService;

    public static String appName;

    @Bean
    public org.springframework.amqp.core.Queue queue(){
        String queneName = new Base64UrlNamingStrategy(appName + ".").generateName();
        log.info("队列的名称是:{}",queneName);
        return new org.springframework.amqp.core.Queue(queneName, false);
    }

    /**
     * #{queue.name}  Spring SPEL表达式
     * @param messageObj
     */
    @RabbitListener(bindings = @QueueBinding(
            value = @Queue(value = "#{queue.name}", durable = "false"),
            exchange = @Exchange(
                    value = BusConfig.EXCHANGE_NAME,
                    ignoreDeclarationExceptions = "true",
                    type = ExchangeTypes.TOPIC
            ),
            key = {BusConfig.ROUTING_KEY}
    ))
    @RabbitHandler
    public void process(Message messageObj, Channel channel) {
        String message = new String(messageObj.getBody(), StandardCharsets.UTF_8);
        log.info("Received Message:<{}>", message);
        // 待实现动态del路由
        RouteDefinitionMessage routeDefinitionMessage = JSON.parseObject(message, RouteDefinitionMessage.class);
        int tag = routeDefinitionMessage.getTag();
        log.info("Received Message tag:<{}>", tag);

        RouteDefinition routeDefinition = routeDefinitionMessage.getRouteDefinition();
        log.info("Received Message routeDefinition:<{}>", routeDefinition);

        if(tag==RouteDefinitionMessageTagEnum.ADD.getKey().intValue()){
            routeService.save(routeDefinition);
        }else if(tag==RouteDefinitionMessageTagEnum.UPDATE.getKey().intValue()){
            routeService.update(routeDefinition);
        }else if(tag==RouteDefinitionMessageTagEnum.DEL.getKey().intValue()){
            routeService.delete(routeDefinition.getId());
        }else{
            log.warn("routeDefinitionMessage的tag出错!!!");
        }
        try {
            channel.basicAck(messageObj.getMessageProperties().getDeliveryTag(), false);
        } catch (IOException e) {
            e.printStackTrace();
        }

    }

    //直接用的@value  也可以通过 environment等去获取
    @Value("${spring.application.name}")
    public void setAppName(String name) {
        appName = name;
    }
}
